package com.kai.service.sms.service.impl;

import cn.hutool.core.lang.Validator;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.kai.service.data.request.sms.CheckSmsMailRequest;
import com.kai.service.data.request.sms.SendSmsMailRequest;
import com.kai.service.enums.ResultCodeEnum;
import com.kai.service.enums.SmsMailCategoryEnum;
import com.kai.service.enums.SmsMailCertifiedEnum;
import com.kai.service.exception.GenericException;
import com.kai.service.sms.entity.SmsMail;
import com.kai.service.util.MailUtil;
import com.kai.service.sms.mapper.SmsMailMapper;
import com.kai.service.sms.service.ISmsMailService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.kai.service.enums.SmsMailTemplateEnum;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.Random;

/**
 * <p>
 * 短信，邮件发送记录表 服务实现类
 * </p>
 *
 * @author wjk
 * @since 2022-03-07
 */
@Service
public class SmsMailServiceImpl extends ServiceImpl<SmsMailMapper, SmsMail> implements ISmsMailService {

    @Autowired
    private MailUtil mailUtil;

    /**
     * 发送验证码
     *
     * @param sendSmsMailRequest
     * @return
     */
    @Override
    public Boolean sendSmsVerificationCode(SendSmsMailRequest sendSmsMailRequest) {
        String username = sendSmsMailRequest.getUsername();
        Integer smsType = sendSmsMailRequest.getSmsType();

        String subject = SmsMailTemplateEnum.getSubjectByCode(smsType);
        String content = SmsMailTemplateEnum.getContentByCode(smsType);
        Integer verificationCode = getSmsVerificationCode();

        String category = "";
        if (Validator.isEmail(username)) {
            category = SmsMailCategoryEnum.EMAIL.toString();
            mailUtil.sendSimpleMail(sendSmsMailRequest.getUsername(), subject, String.format(content, verificationCode));
        } else if (Validator.isMobile(username)) {
            // TODO: 2022/3/8 短信
            category = SmsMailCategoryEnum.SMS.toString();
            return Boolean.TRUE;
        } else {
            throw new GenericException(ResultCodeEnum.INCORRECT_ACCOUNT_FORMAT);
        }

        // 保存短信记录
        SmsMail smsMail = new SmsMail();
        smsMail.setUsername(username)
                .setVerificationCode(verificationCode)
                .setCodeCertified(SmsMailCertifiedEnum.NO.getCode())
                .setCreateDatetime(new Date())
                .setCategory(category);

        return this.save(smsMail);
    }

    /**
     * 校验验证码
     *
     * @param checkSmsMailRequest
     * @return
     */
    @Override
    public Boolean checkSmsVerificationCode(CheckSmsMailRequest checkSmsMailRequest) {
        long nowTimestamp = System.currentTimeMillis();
        String username = checkSmsMailRequest.getUsername();
        Integer verificationCode = checkSmsMailRequest.getVerificationCode();

        SmsMail smsMail = this.getOne(new LambdaQueryWrapper<SmsMail>()
                .eq(SmsMail::getUsername, username)
                .eq(SmsMail::getVerificationCode, verificationCode)
                .eq(SmsMail::getCodeCertified, SmsMailCertifiedEnum.NO.getCode())
                .orderByDesc(SmsMail::getCreateDatetime)
                .last("limit 1"));
        if (null == smsMail){
            throw new GenericException(ResultCodeEnum.INCORRECT_VERIFICATION_CODE);
        }
        long dbTimestamp = smsMail.getCreateDatetime().getTime();
        if ((dbTimestamp + (5 * 60 * 1000)) < nowTimestamp){
            throw new GenericException(ResultCodeEnum.INCORRECT_VERIFICATION_CODE);
        }

        return smsMail.setCodeCertified(SmsMailCertifiedEnum.YES.getCode()).updateById();
    }

    /**
     * 生成六位随机数
     *
     * @return
     */
    public Integer getSmsVerificationCode() {
        StringBuilder code = new StringBuilder();
        Random random = new Random();
        for (int i = 0; i < 6; i++) {
            code.append(random.nextInt(10));
        }
        return Integer.valueOf(code.toString());
    }

}
